package org.ezplatform.office.calendar.util;

import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.charset.Charset;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;
import org.apache.http.client.methods.HttpDelete;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import org.apache.commons.collections.CollectionUtils;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.client.HttpClient;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ssl.NoopHostnameVerifier;
import org.apache.http.conn.ssl.TrustStrategy;
import org.apache.http.entity.ContentType;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.protocol.BasicHttpContext;
import org.apache.http.ssl.SSLContexts;
import org.apache.http.util.EntityUtils;
import org.ezplatform.mobile.cocall.util.FileUtils;
import org.ezplatform.sdk.AccessToken;
import org.ezplatform.sdk.Client;
import org.ezplatform.util.DateUtils;
import org.ezplatform.util.GlobalConstant;
import org.ezplatform.util.StringUtils;
import org.ezplatform.util.ValidateUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;

/**
 * 日程工具类
 * 此处方法用于时间计算，简单的数据处理
 */

public class CalendarUtils {
    private final static Logger LOG = LoggerFactory.getLogger(CalendarUtils.class);

    /**
     * 根据字符串获取日期格式时间
     *
     * @param dataStr:字符串形式的时间
     * @param dateType:日期格式，如：yyyy-MM-dd
     * @return
     * @throws ParseException
     */
    public static Date getDataByStr(String dataStr, String dateType){
        try {
            SimpleDateFormat sdf = new SimpleDateFormat(dateType);
            return sdf.parse(dataStr);
        }catch (Exception e){
            LOG.error("时间转换错误",e);
        }
        return null;
    }

    /**
     * 获取字符串格式的时间
     *
     * @param date:时间值
     * @param dateType:日期格式，如：yyyy-MM-dd
     * @return
     */
    public static String getStrByDate(Date date, String dateType) {
        SimpleDateFormat sdf = new SimpleDateFormat(dateType);
        return sdf.format(date);
    }

    /**
     * 字符串格式的时间比较大小
     *
     * @param date1:字符串形式的时间
     * @param date2:字符串形式的时间
     * @param dateType:日期格式，如：yyyy-MM-dd
     * @return:int类型0表示相等，1表示date1大于date2,2表示date1小于date2
     */
    public static int compareDateStr(String date1, String date2) {
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
        try {
            Date dt1 = df.parse(date1);
            Date dt2 = df.parse(date2);
            if (dt1.getTime() > dt2.getTime()) {
                return 1;
            } else if (dt1.getTime() < dt2.getTime()) {
                return 2;
            } else {
                return 0;
            }
        } catch (Exception exception) {
            LOG.error("转换时间异常", exception);
            return 3;
        }
    }

    /**
     * 时间比较大小
     *
     * @param date1:时间
     * @param date2:时间
     * @return:int类型0表示相等，1表示date1大于date2,2表示date1小于date2
     */
    public static int compareDate(Date date1, Date date2) {
        try {
            if (date1.getTime() > date2.getTime()) {
                return 1;
            } else if (date1.getTime() < date2.getTime()) {
                return 2;
            } else {
                return 0;
            }
        } catch (Exception exception) {
            LOG.error("获取时间异常", exception);
        }
        return 0;
    }

    /**
     * 计算两个字符串格式的日期之间的天数
     *
     * @param date1
     * @param date2
     * @param dateType
     * @return
     */
    public static int countDateStrDays(String date1, String date2, String dateType) {
        long result = 0;
        DateFormat df = new SimpleDateFormat(dateType);
        try {
            Date dt1 = df.parse(date1);
            Date dt2 = df.parse(date2);
            result = DateUtils.getDiffDay(dt1, dt2);
        } catch (Exception e) {
            LOG.error("时间转换异常", e);
        }
        return (int) result;
    }

    /**
     * 给日期增加天数
     *
     * @param date 给定的时间
     * @param days 要增加的天数
     * @param dateType 日期格式  yyyy-MM-dd HH:mm:ss 或 yyyy-MM-dd
     * @return 返回字符串形式的日期
     */
    public static String addDays(String date, int days, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        try {
            Date dt = df.parse(date);
            result = df.format(DateUtils.addDays(dt, days));
        } catch (Exception e) {
            LOG.error("给日期增加天数异常", e);
        }
        return result;
    }

    /**
     * 给日期增加月份(只改变月份，当新增的月份没有传入的日期时，为新增月份最后一天)
     *
     * @param date 初始时间
     * @param dateType 日期格式
     * @param addNumber 增加的月份
     * @return 增加后的日期字符串
     */
    public static String addMonthsLimit(String date, String dateType, int addNumber) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        Date resultDate;
        try {
            resultDate = df.parse(date);
            Calendar c = Calendar.getInstance();
            c.setTime(resultDate);
            c.add(Calendar.MONTH, addNumber);
            result = df.format(c.getTime());
        } catch (Exception e) {
            LOG.error("给日期增加月份异常", e);
        }
        return result;
    }

    /**
     * 给日期增加月份(只改变月份，当新增的月份没有传入的日期时，月份继续增加)
     *
     * @param date
     * @param months
     * @param dateType
     * @return
     */
    public static String addMonths(String date, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        Date resultDate = new Date();
        try {
            resultDate = df.parse(date);
            Calendar c = Calendar.getInstance();
            c.setTime(resultDate);
            int day = c.get(Calendar.DATE);
            resultDate = DateUtils.addMonths(resultDate, 1);
            c.setTime(resultDate);
            int d = c.get(Calendar.DATE);
            if (day != d) {
                resultDate = DateUtils.addMonths(resultDate, 1);
                resultDate = DateUtils.setDays(resultDate, day);
            }
            result = df.format(resultDate);
        } catch (Exception e) {
            LOG.error("给日期增加月份异常", e);
        }
        return result;
    }

    /**
     * 给日期增加年份
     *
     * @param date
     * @param years
     * @param dateType
     * @return
     */
    public static String addYears(String date, int years, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        try {
            Date dt = df.parse(date);
            result = df.format(DateUtils.addYears(dt, years));
        } catch (Exception e) {
            LOG.error("给日期增加年份异常", e);
        }
        return result;
    }

    /**
     * 得到当期时间的周系数。星期日：7，星期一：1，星期二：2，星期三：3，星期四：4，星期五：5，星期六：6
     *
     * @param date
     * @param dateType
     * @return
     */
    public static int dayForWeek(String date, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        int result = 0;
        try {
            Date date1 = df.parse(date);
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date1);
            result = calendar.get(Calendar.DAY_OF_WEEK);
            if (result == 1) {
                result = 7;
            } else {
                result = result - 1;
            }
        } catch (Exception e) {
            LOG.error("得到当期时间的周系数异常", e);
        }
        return result;
    }

    /**
     * 得到当期时间为星期几
     *
     * @param date
     * @param dateType
     * @return
     */
    public static String dayOfWeek(String date, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        int result = 0;
        String weekName = "";
        try {
            Date date1 = df.parse(date);
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date1);
            result = calendar.get(Calendar.DAY_OF_WEEK);
            if (result == 1) {
                result = 7;
            } else {
                result = result - 1;
            }
            if (result == 1) {
                weekName = "星期一";
            } else if (result == 2) {
                weekName = "星期二";
            } else if (result == 3) {
                weekName = "星期三";
            } else if (result == 4) {
                weekName = "星期四";
            } else if (result == 5) {
                weekName = "星期五";
            } else if (result == 6) {
                weekName = "星期六";
            } else if (result == 7) {
                weekName = "星期日";
            }
        } catch (Exception e) {
            LOG.error("得到当期时间为星期几异常", e);
        }
        return weekName;
    }

    /**
     * 得到当期时间为周几
     *
     * @param date
     * @param dateType
     * @return
     */
    public static String dayOfWeek2(String date, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        int result = 0;
        String weekName = "";
        try {
            Date date1 = df.parse(date);
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date1);
            result = calendar.get(Calendar.DAY_OF_WEEK);
            if (result == 1) {
                result = 7;
            } else {
                result = result - 1;
            }
            if (result == 1) {
                weekName = "周一";
            } else if (result == 2) {
                weekName = "周二";
            } else if (result == 3) {
                weekName = "周三";
            } else if (result == 4) {
                weekName = "周四";
            } else if (result == 5) {
                weekName = "周五";
            } else if (result == 6) {
                weekName = "周六";
            } else if (result == 7) {
                weekName = "周日";
            }
        } catch (Exception e) {
            LOG.error("得到当期时间为周几异常", e);
        }
        return weekName;
    }

    /**
     * 设置日期的日(如果当前月没有该日期，就增加一个月)
     *
     * @param date
     * @param day
     * @param dateType
     * @return
     */
    public static String setDay(String date, String day, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        try {
            Date dt = df.parse(date);
            Calendar c = Calendar.getInstance();
            c.setTime(dt);
            int days = c.getActualMaximum(Calendar.DAY_OF_MONTH);
            if (days < Integer.parseInt(day)) {
                dt = DateUtils.addMonths(dt, 1);
            }
            result = df.format(DateUtils.setDays(dt, Integer.parseInt(day)));
        } catch (Exception e) {
            LOG.error("设置日期的日异常", e);
        }
        return result;
    }

    /**
     * 获取日期所在月的周数
     *
     * @param year
     * @param month
     * @return
     */
    public static int getWeekOfMonth(String year, String month) {
        Calendar c = Calendar.getInstance();
        c.set(Calendar.YEAR, Integer.parseInt(year));
        c.set(Calendar.MONTH, Integer.parseInt(month) - 1);
        c.setFirstDayOfWeek(java.util.Calendar.MONDAY);
        return c.getActualMaximum(Calendar.WEEK_OF_MONTH);
    }

    /**
     * 获取给定日期的当前周的第一天
     *
     */
    public static String getWeekFirstDay(String dataStr){
        String firstWeekDay = "";
        try {
            SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
            Date date = df.parse(dataStr);
            Calendar cal = Calendar.getInstance();

            cal.setTime(date);
            //判断要计算的日期是否是周日，如果是则减一天计算周六的，否则会出问题，计算到下一周去了
            int dayWeek = cal.get(Calendar.DAY_OF_WEEK);//获得当前日期是一个星期的第几天
            if(1 == dayWeek) {
                cal.add(Calendar.DAY_OF_MONTH, -1);
            }

            cal.set(Calendar.DAY_OF_WEEK, Calendar.MONDAY); // 获取本周一的日期

            firstWeekDay = df.format(cal.getTime());

        }catch (Exception e){
            LOG.error("获取给定日期的当前周第一天失败",e);
        }

        return firstWeekDay;
    }

    /**
     * 获取给定日期当前周的最后一天
     *
     *
     */
    public static String getWeekLastDay(String dataStr){
        String lastWeekDay = "";
        try {
            SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
            Date date = df.parse(dataStr);
            Calendar cal = Calendar.getInstance();

            cal.setTime(date);
            //判断要计算的日期是否是周日，如果是则减一天计算周六的，否则会出问题，计算到下一周去了
            int dayWeek = cal.get(Calendar.DAY_OF_WEEK);//获得当前日期是一个星期的第几天
            if(1 == dayWeek) {
                cal.add(Calendar.DAY_OF_MONTH, -1);
            }

            cal.set(Calendar.DAY_OF_WEEK, Calendar.SUNDAY);
            cal.add(Calendar.WEEK_OF_YEAR, 1);

            lastWeekDay = df.format(cal.getTime());

        }catch (Exception e){
            LOG.error("获取给定日期的当前周第一天失败",e);
        }

        return lastWeekDay;
    }


    /**
     * 设置日期的日(如果当前月没有该日期，就选择最后一天)
     *
     * @param date
     * @param day
     * @param dateType
     * @return
     */
    public static String setDayLimit(String date, String day, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        try {
            Date dt = df.parse(date);
            Calendar c = Calendar.getInstance();
            c.setTime(dt);
            int days = c.getActualMaximum(Calendar.DAY_OF_MONTH);
            int nowDay = Integer.parseInt(date.split(" ")[0].split("-")[2]);
            if (nowDay <= Integer.parseInt(day)) {
                c.set(Calendar.DAY_OF_MONTH, Integer.parseInt(day));
                if (days < Integer.parseInt(day)) {
                    c.set(Calendar.DAY_OF_MONTH, days);
                }
            }
            result = df.format(c.getTime());
        } catch (Exception e) {
            LOG.error("设置日期的日异常", e);
        }
        return result;
    }

    /**
     * 根据月日获取当前月的最后一天
     *
     * @param year
     * @param month
     * @param dateType
     * @return
     */
    public static String getLastDayOfMonth(String date, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        try {
            Date dt = df.parse(date);
            Calendar c = Calendar.getInstance();
            c.setTime(dt);
            int days = c.getActualMaximum(Calendar.DAY_OF_MONTH);
            c.set(Calendar.DAY_OF_MONTH, days);
            result = df.format(c.getTime());
        } catch (Exception e) {
            LOG.error("根据月日获取当前月的最后一天异常", e);
        }
        return result;
    }

    /**
     * 设置日期的日和月
     *
     * @param date
     * @param monthDay
     * @param dateType
     * @return
     */
    public static String setMonthAndDay(String date, String monthDay, String dateType) {
        SimpleDateFormat df = new SimpleDateFormat(dateType);
        String result = "";
        int day = Integer.parseInt(monthDay.substring(monthDay.length() - 2, monthDay.length()));
        int month = Integer.parseInt(monthDay.substring(0, monthDay.length() - 2));
        Calendar ca = Calendar.getInstance();
        try {
            Date dt = df.parse(date);
            ca.setTime(dt);
            if ("229".equals(monthDay)) {
                int year = ca.get(Calendar.YEAR);
                while (true) {
                    if (year % 4 == 0 && year % 100 != 0 || year % 400 == 0) {
                        dt = DateUtils.setYears(dt, year);
                        break;
                    } else {
                        year++;
                    }
                }
            }
            dt = DateUtils.setMonths(dt, month - 1);
            dt = DateUtils.setDays(dt, day);
            result = df.format(dt);
        } catch (Exception e) {
            LOG.error("设置日期的日和月异常", e);
        }
        return result;
    }

    /**
     * 将秒转换为固定格式的时间 HH:mm
     *
     * @param seconds
     * @return
     */
    public static String getTime(int seconds) {
        StringBuffer result = new StringBuffer();
        int hour = seconds / (60 * 60);
        int min = (seconds - hour * 60 * 60) / 60;
        result.append(hour < 10 ? "0" + hour + ":" : hour + ":");
        result.append(min < 10 ? "0" + min : min);
        return result.toString();
    }

    /**
     * 将时间转换为秒数
     *
     * @param seconds
     * @return
     */
    public static int getSecondsByStrDate(String date) {
        String[] dStr = null;
        if (date.contains("T")) {
            dStr = date.split("T");
        } else {
            dStr = date.split(" ");
        }
        int time = 0;
        if (dStr.length == 2) {
            time = getSeconds(dStr[1]);
        }
        return time;
    }

    /**
     * 根据时间获取秒数
     *
     * @param time
     * @return
     */
    public static int getSeconds(String time) {
        int result = 0;
        String[] times = time.split(":");
        result = Integer.parseInt(times[0]) * 3600 + Integer.parseInt(times[1]) * 60;
        return result;
    }

    /**
     * 获得该月第一天
     *
     * @param year
     * @param month
     * @return
     */
    public static String getFirstDayOfMonth(int year, int month) {
        Calendar cal = Calendar.getInstance();
        //设置年份
        cal.set(Calendar.YEAR, year);
        //设置月份
        cal.set(Calendar.MONTH, month - 1);
        //获取某月最小天数
        int firstDay = cal.getActualMinimum(Calendar.DAY_OF_MONTH);
        //设置日历中月份的最小天数
        cal.set(Calendar.DAY_OF_MONTH, firstDay);
        //格式化日期
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        String firstDayOfMonth = sdf.format(cal.getTime());
        return firstDayOfMonth;
    }

    /**
     * 获得该月最后一天
     *
     * @param year
     * @param month
     * @return
     */
    public static String getLastDayOfMonth(int year, int month) {
        Calendar cal = Calendar.getInstance();
        //设置年份
        cal.set(Calendar.YEAR, year);
        //设置月份
        cal.set(Calendar.MONTH, month - 1);
        //获取某月最大天数
        int lastDay = cal.getActualMaximum(Calendar.DAY_OF_MONTH);
        //设置日历中月份的最大天数
        cal.set(Calendar.DAY_OF_MONTH, lastDay);
        //格式化日期
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        String lastDayOfMonth = sdf.format(cal.getTime());
        return lastDayOfMonth;
    }

    /**
     * 获得两个日期之间的月份的开始日期和结束日期
     *
     * @param year
     * @param month
     * @return
     */
    public static String[] getMonthInTwoDate(String start, String end) {
        SimpleDateFormat df = new SimpleDateFormat("yyyy-MM");
        String[] result = new String[2];
        try {
            Date startDate = df.parse(start);
            Date endDate = df.parse(end);
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(startDate);
            int days = calendar.getActualMaximum(Calendar.DAY_OF_MONTH);
            calendar.add(Calendar.MONTH, 1);
            String month = "";
            if (calendar.getTime().before(endDate)) {
                days = calendar.getActualMaximum(Calendar.DAY_OF_MONTH);
                month = df.format(calendar.getTime());
            } else {
                month = df.format(startDate);
            }
            result[0] = month + "-1";
            result[1] = month + "-" + days;
        } catch (ParseException e) {
            LOG.error("获得两个日期之间的月份的开始日期和结束日期异常", e);
        }
        return result;
    }

    // 获取本周开始时间
    public static Date getBeginDayOfWeek() {
        Date date = new Date();
        Calendar cal = Calendar.getInstance();
        cal.setTime(date);
        int dayofweek = cal.get(Calendar.DAY_OF_WEEK);
        if (dayofweek == 1) {
            dayofweek += 7;
        }
        cal.add(Calendar.DATE, 2 - dayofweek);
        Date weekStartTime = cal.getTime();
        return weekStartTime;
    }

    // 获取本周结束时间
    public static Date getEndDayOfWeek() {
        Calendar cal = Calendar.getInstance();
        cal.setTime(getBeginDayOfWeek());
        cal.add(Calendar.DAY_OF_WEEK, 6);
        Date weekEndSta = cal.getTime();
        return weekEndSta;
    }

    /**
     * 根据时间获取秒数
     *
     * @param time
     * @return
     */
    public static int getWeekNum(String today) {
        SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
        Date date = null;
        try {
            date = format.parse(today);
        } catch (ParseException e) {
            LOG.error("根据时间获取秒数异常", e);
        }
        Calendar calendar = Calendar.getInstance();
        calendar.setFirstDayOfWeek(Calendar.MONDAY);
        calendar.setTime(date);
        return calendar.get(Calendar.WEEK_OF_YEAR);
    }

    /**
     * 把字符串毫秒值转换为日期格式
     *
     * @param time
     * @return
     */
    public static Date stringToDate(String time, String dateType) throws ParseException {
        Long L = Long.parseLong(time);
        Date date = new Date(L);
        DateFormat dateFormat = new SimpleDateFormat(dateType);
        return getDataByStr(dateFormat.format(date), dateType);
    }

    /**
     * 获得某年第几周的开始时间和结束时间
     *
     * @param year
     * @param week
     * @return
     */
    public static String[] getMonthInTwoDate(int year, int week) {
        Calendar calendar = Calendar.getInstance();
        String[] weeks = new String[2];
        calendar.set(year, 0, 1);
        int dayOfWeek = 7 - calendar.get(Calendar.DAY_OF_WEEK) + 2;
        week = week - 2;//周数减去第一周再减去要得到的周
        calendar.add(Calendar.DAY_OF_YEAR, week * 7 + dayOfWeek);
        weeks[0] = new SimpleDateFormat("yyyy年MM月dd日").format(calendar.getTime());
        calendar.add(Calendar.DAY_OF_YEAR, 6);
        weeks[1] = new SimpleDateFormat("yyyy年MM月dd日").format(calendar.getTime());
        return weeks;
    }

    /**
     * 获取指定开始/结束时间所有的日期
     *
     * @param startTime
     * @param endTime
     * @return
     */
    public static List<String> getDays(String startTime, String endTime) {
        // 返回的日期集合
        List<String> days = new ArrayList<>();
        DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
        try {
            Date start = dateFormat.parse(startTime);
            Date end = dateFormat.parse(endTime);

            Calendar tempStart = Calendar.getInstance();
            tempStart.setTime(start);

            Calendar tempEnd = Calendar.getInstance();
            tempEnd.setTime(end);
            tempEnd.add(Calendar.DATE, +1);// 日期加1(包含结束)
            while (tempStart.before(tempEnd)) {
                days.add(dateFormat.format(tempStart.getTime()));
                tempStart.add(Calendar.DAY_OF_YEAR, 1);
            }
        } catch (ParseException e) {
            LOG.error("时间转换异常", e);
        }
        return days;
    }

    /**
     * 判断今天所在的年份和本周日所在的年份是否同一年，true:是，false:否
     *
     * @param today
     * @return
     */
    public static boolean isSameYear(String today) {
        Boolean result = true;
        SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
        Date date = null;
        try {
            date = format.parse(today);
        } catch (ParseException e) {
            LOG.error("时间转换异常", e);
        }
        Calendar calendar = Calendar.getInstance();
        calendar.setFirstDayOfWeek(Calendar.MONDAY);
        calendar.setTime(date);
        //今天所在的年份
        int todayOfYear = calendar.get(Calendar.YEAR);
        int dayOfWeek = calendar.get(Calendar.DAY_OF_WEEK) - 1 == 0 ? 7 : calendar.get(Calendar.DAY_OF_WEEK) - 1;
        calendar.add(Calendar.DATE, -dayOfWeek + 7);
        //本周周日所在的年份
        int sundayOfYear = calendar.get(Calendar.YEAR);
        if (todayOfYear != sundayOfYear) {
            result = false;
        }
        return result;
    }


    /**
     * 获取当前时间当前月的第一天开始时间
     *
     * @return
     */
    public static String getMonthDateBegin() {
        Date today = new Date();
        SimpleDateFormat dateTimeFormat = new SimpleDateFormat("yyyy-MM-dd");
        Calendar c = Calendar.getInstance();
        c.setTime(today);
        c.set(Calendar.DAY_OF_MONTH, 1);
        c.set(Calendar.HOUR_OF_DAY, 0);
        c.set(Calendar.MINUTE, 0);
        c.set(Calendar.SECOND, 0);
        String dateBegin = dateTimeFormat.format(c.getTime());
        return dateBegin;
    }

    /**
     * 获取当前时间当前月的最后一天结束时间
     *
     * @return
     */
    public static String getMonthDateEnd() {
        Date today = new Date();
        SimpleDateFormat dateTimeFormat = new SimpleDateFormat("yyyy-MM-dd");
        Calendar c = Calendar.getInstance();
        c.setTime(today);
        c.set(Calendar.DAY_OF_MONTH, c.getActualMaximum(Calendar.DAY_OF_MONTH));
        c.set(Calendar.HOUR_OF_DAY, 23);
        c.set(Calendar.MINUTE, 59);
        c.set(Calendar.SECOND, 59);
        String dateEnd = dateTimeFormat.format(c.getTime());
        return dateEnd;
    }

    /**
     * 获取给定时间字符串所在周的第一天日期字符串
     *
     **/
    public static String getWeekFirstDayStr(String dateStr) throws ParseException {
        java.util.Calendar cal = java.util.Calendar.getInstance();
        cal.setTime(getDataByStr(dateStr, "yyyy-MM-dd"));
        cal.setFirstDayOfWeek(java.util.Calendar.MONDAY);
        cal.set(java.util.Calendar.DAY_OF_WEEK,java.util.Calendar.MONDAY);
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        dateStr = sdf.format(cal.getTime());
        return dateStr;
    }


    /**
     * 针对List<Map<String, String>> 排序 时间类型
     * @param resultList 要排序的List<Map<String, String>>结合
     * @param keyStrOne 每个元素中要判断的字段1
     *
     */
    public static void sortResultList(List<Map<String, String>> resultList, String keyStrOne, String keyStrTwo) {
        Collections.sort(resultList, new Comparator<Map<String,String>>(){
            @Override
            public int compare(Map<String,String> o1, Map<String,String> o2) {
                SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm");
                Date date1 = null;
                Date date2 = null;
                try {
                    //全天日程下，自动补齐时分
                    date1 = format.parse(StringUtils.equals(o1.get(keyStrOne), "1")?o1.get(keyStrTwo)+" 00:00":o1.get(keyStrTwo));
                    date2 = format.parse(StringUtils.equals(o2.get(keyStrOne), "1")?o2.get(keyStrTwo)+" 00:00":o2.get(keyStrTwo));
                }catch (ParseException e) {
                    LOG.error("时间转换异常",e);
                }
                return date1.compareTo(date2);
            }
        });
    }

    /**
     * 针对List<Map<String, Object>> 排序 按照关键字段升序排序
     * @param resultList 要排序的List<Map<String, String>>结合
     * @param keyStr 没个元素中要判断的字段1
     *
     */
    public static void sortResultList(List<Map<String, Object>> resultList, String keyStr) {
        Collections.sort(resultList, new Comparator<Map<String, Object>>() {
            @Override
            public int compare(Map<String, Object> o1, Map<String, Object> o2) {
                if (o1.get(keyStr) == null && o2.get(keyStr) == null) {
                    return 0;
                }
                if (o1.get(keyStr) == null) {
                    return -1;
                }
                if (o2.get(keyStr) == null) {
                    return 1;
                }
                return Long.valueOf(o1.get(keyStr).toString()).compareTo(Long.valueOf(o2.get(keyStr).toString()));
            }
        });
    }

    /**
     * 针对上午下午进行排序
     * 上午排在上面
     *
     */
    public static void sortResultListByAmOrPm(List<Map<String, Object>> resultList) {
        Collections.sort(resultList, new Comparator<Map<String, Object>>() {
            @Override
            public int compare(Map<String, Object> o1, Map<String, Object> o2) {
                if (o1.get("isAmOrPm") == null && o2.get("isAmOrPm") == null) {
                    return 0;
                }
                if (o1.get("isAmOrPm") == null) {
                    return -1;
                }
                if (o2.get("isAmOrPm") == null) {
                    return 1;
                }
                return Long.valueOf(o2.get("isAmOrPm").toString()).compareTo(Long.valueOf(o1.get("isAmOrPm").toString()));
            }
        });
    }

    /**
     * 针对List<Map<String, String>> 排序 按照关键字段升序排序
     * @param resultList 要排序的List<Map<String, String>>结合
     * @param keyStr 没个元素中要判断的字段1
     *
     */
    public static void sortResultListString(List<Map<String, String>> resultList, String keyStr) {
        Collections.sort(resultList, new Comparator<Map<String, String>>() {
            @Override
            public int compare(Map<String, String> o1, Map<String, String> o2) {
                Integer int1 = Integer.valueOf(o1.get(keyStr));
                Integer int2 = Integer.valueOf(o2.get(keyStr));
                return int2.compareTo(int1);
            }
        });
    }

    /**
     * 时间排序 List<String>
     *
     */
    public static void sortListString(List<String> resultList) {
        // 排序
        Collections.sort(resultList, new Comparator<String>() {
            @Override
            public int compare(String o1, String o2) {
                SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
                Date date1 = null;
                Date date2 = null;
                try {
                    date1 = format.parse(o1);
                    date2 = format.parse(o2);
                } catch (ParseException e) {
                    LOG.error("时间转换异常",e);
                }
                return date2.compareTo(date1);
            }
        });
    }

    /**
     * 特殊字符的替换
     *
     */
    public static void replaceSpecial (List<Map<String,Object>> resultList){
        if(CollectionUtils.isNotEmpty(resultList)){
            for(Map<String,Object> result : resultList){
                String title = StringUtils.null2String(result.get("title"));
                if(StringUtils.isNotEmpty(title)){
                    result.put("title",title.replace("flexbracketB","[").replace("flexbracketE","]"));
                }
                String content = StringUtils.null2String(result.get("content"));
                if(StringUtils.isNotEmpty(content)){
                    result.put("content",content.replace("flexbracketB","[").replace("flexbracketE","]"));
                }
                String address = StringUtils.null2String(result.get("address"));
                if(StringUtils.isNotEmpty(address)){
                    result.put("address",address.replace("flexbracketB","[").replace("flexbracketE","]"));
                }
            }
        }
    }


    /**
     * 获取给定月的当月最大天数  如 5月  month=4(calendar类默认1月是0)
     * @param year
     * @param month
     * @return
     */
    public static int getMonthMaxDay(Integer year, Integer month) {
        Calendar c = Calendar.getInstance();
        c.set(Calendar.YEAR, year); // 2010年
        c.set(Calendar.MONTH, month); // 6 月
        return c.getActualMaximum(Calendar.DAY_OF_MONTH);
    }

    /**
     * 验证选人组件参数合法性
     *
     */
    public static boolean verifyScopeStr(String scopeValue){
        try {
            if(StringUtils.isNotBlank(scopeValue)){
                List<Map<String,String>> mapPermitList = (List<Map<String,String>>) JSONArray.parse(scopeValue);
                List<String> keysList = new ArrayList<>();
//                keysList.add("orgId");
//                keysList.add("scopeType");
//                keysList.add("scopeName");
//                keysList.add("orgPath");
                if(!ValidateUtils.validateScopeList(mapPermitList,keysList)){
                    return false;
                }
            }

            return true;
        }catch (Exception e){
            LOG.error("选人组件字符串传入错误",e);
            return false;
        }
    }

    /**
     * http、https post请求
     *
     */
    public static JSONObject httpPost(String url, Object data) throws Exception {
        HttpPost httpPost = new HttpPost(url);
        CloseableHttpResponse response = null;
        CloseableHttpClient httpClient = HttpClients.createDefault();
        if(url.contains("https:")){
            httpClient = getIgnoeSSLClient();
        }
        RequestConfig requestConfig = RequestConfig.custom().
                setSocketTimeout(2000).setConnectTimeout(2000).build();
        httpPost.setConfig(requestConfig);
        httpPost.addHeader("Content-Type", "application/json;charset=utf-8");

        try {
            StringEntity requestEntity = new StringEntity(JSON.toJSONString(data), ContentType.APPLICATION_JSON);
            httpPost.setEntity(requestEntity);

            response = httpClient.execute(httpPost, new BasicHttpContext());

            if (response.getStatusLine().getStatusCode() != 200) {

                return null;
            }
            HttpEntity entity = response.getEntity();
            if (entity != null) {
                String resultStr = EntityUtils.toString(entity, "utf-8");

                JSONObject result = JSON.parseObject(resultStr);
                return result;
            }
        } catch (IOException e) {
            LOG.error("调用接口出错",e);
            return null;
        } finally {
            if (response != null) try {
                response.close();
            } catch (IOException e) {
                LOG.error("调用接口出错",e);
            }
        }

        return null;
    }

    /**
     * 获取忽略证书验证的client
     *
     * @return
     * @throws Exception
     */
    public static CloseableHttpClient getIgnoeSSLClient() throws Exception {
        SSLContext sslContext = SSLContexts.custom().loadTrustMaterial(null, new TrustStrategy() {
            @Override
            public boolean isTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {
                return true;
            }
        }).build();

        //创建httpClient
        CloseableHttpClient client = HttpClients.custom().setSSLContext(sslContext).
                setSSLHostnameVerifier(new NoopHostnameVerifier()).build();
        return client;
    }

    public static JSONObject doPost(String url, Map<String,Object> paramMap) {
        String result = null;
        JSONObject resultJsonObject = null;
        HttpURLConnection httpConnection = null;
        try {

            httpConnection = createConnection(url,"POST",null,paramMap!=null ? JSON.toJSONString(paramMap) : "");

            String encoding = "UTF-8";
            if (httpConnection.getContentType() != null && httpConnection.getContentType().indexOf("charset=") >= 0) {
                encoding = httpConnection.getContentType().substring(httpConnection.getContentType().indexOf("charset=") + 8);
            }
            result = inputStream2String(httpConnection.getInputStream(),encoding);
            resultJsonObject = JSON.parseObject(result);
        } catch (Exception e) {
            LOG.error("调用接口出错",e);
        } finally {
            if (httpConnection != null) {
                httpConnection.disconnect();
            }
        }
        return resultJsonObject;
    }


    /**
     * 读取inputStream 到 string
     * @param input
     * @param encoding
     * @return
     * @throws IOException
     */
    private static String inputStream2String(InputStream input, String encoding) throws IOException {
        BufferedReader reader = new BufferedReader(new InputStreamReader(input,
                encoding));
        StringBuilder result = new StringBuilder();
        String temp = null;
        while ((temp = reader.readLine()) != null) {
            result.append(temp);
        }

        return result.toString();
    }

    /**
     * 创建HTTP连接
     *
     * @param url
     *            地址
     * @param method
     *            方法
     * @param headerParameters
     *            头信息
     * @param body
     *            请求内容
     * @returngetRequestBody
     * @throws Exception
     */
    private static HttpURLConnection createConnection(String url, String method, Map<String, String> headerParameters, String body) {
        HttpURLConnection httpConnection = null;
        try{
            URL Url = new URL(url);

            //https请求忽略ssl证书，该部分必须在获取connection前调用
            if(url.contains("https:")){
                trustAllHttpsCertificates();
                HostnameVerifier hv = new HostnameVerifier() {
                    @Override
                    public boolean verify(String urlHostName, SSLSession session) {
                        return true;
                    }
                };
                HttpsURLConnection.setDefaultHostnameVerifier(hv);
            }

            httpConnection = (HttpURLConnection) Url.openConnection();
            // 设置请求时间
            httpConnection.setConnectTimeout(5000);
            // 设置 header
            if (headerParameters != null) {
                Iterator<String> iteratorHeader = headerParameters.keySet()
                        .iterator();
                while (iteratorHeader.hasNext()) {
                    String key = iteratorHeader.next();
                    httpConnection.setRequestProperty(key,
                            headerParameters.get(key));

                }
            }
            httpConnection.setRequestProperty("Content-Type","application/xml");

            // 设置请求方法
            httpConnection.setRequestMethod(method);
            httpConnection.setDoOutput(true);
            httpConnection.setDoInput(true);
            StringBuffer sBuffer = new StringBuffer();
            // 写query数据流
            if (!(body == null || body.trim().equals(""))) {
                OutputStreamWriter writer = new OutputStreamWriter(httpConnection.getOutputStream(), "utf-8");
                try {
                    writer.write(body);
                }catch (Exception e){
                    //LOG.error(e.getMessage(),e);
                }finally {
                    if (writer != null) {
                        writer.flush();
                        writer.close();
                    }
                }
            }
            // 请求结果
            int responseCode = httpConnection.getResponseCode();
            System.out.println("responseCode="+responseCode);
        }catch(Exception e){
            //LOG.error(e.getMessage(),e);
        }

        return httpConnection;
    }

    private static void trustAllHttpsCertificates() throws Exception {
        javax.net.ssl.TrustManager[] trustAllCerts = new javax.net.ssl.TrustManager[1];
        javax.net.ssl.TrustManager tm = new miTM();
        trustAllCerts[0] = tm;
        javax.net.ssl.SSLContext sc = javax.net.ssl.SSLContext.getInstance("SSL");
        sc.init(null, trustAllCerts, null);
        javax.net.ssl.HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
    }

    static class miTM implements javax.net.ssl.TrustManager, javax.net.ssl.X509TrustManager {
        @Override
        public java.security.cert.X509Certificate[] getAcceptedIssuers() {
            return null;
        }

        public boolean isServerTrusted(java.security.cert.X509Certificate[] certs) {
            return true;
        }

        public boolean isClientTrusted(java.security.cert.X509Certificate[] certs) {
            return true;
        }

        @Override
        public void checkServerTrusted(java.security.cert.X509Certificate[] certs, String authType)
                throws java.security.cert.CertificateException {
            return;
        }

        @Override
        public void checkClientTrusted(java.security.cert.X509Certificate[] certs, String authType)
                throws java.security.cert.CertificateException {
            return;
        }
    }

    public static JSONObject doDel(String url) throws Exception {
        JSONObject jsonObject = null;
        CloseableHttpClient client = HttpClients.createDefault();
        if(url.contains("https:")){
            client = getIgnoeSSLClient();
        }
        HttpDelete httpDelete = new HttpDelete(url);
        HttpResponse httpResponse = client.execute(httpDelete);
        HttpEntity httpEntity = httpResponse.getEntity();
        if (httpEntity != null) {
            String result = EntityUtils.toString(httpEntity, "UTF-8");
            jsonObject =  JSONObject.parseObject(result);
        }
        httpDelete.releaseConnection();
        return jsonObject;
    }


}